# @Time : 2024-11-14 10:36
# @Author : Fioman 
# @Phone : 13149920693
"""
Eap通信相关的一些通用参数以及通信过程中的一些共享变量和参数,设置为单例模式
"""
import threading

from eap_control.data_model import RealStatusData
from eap_control.eap_debug import debug_eap, check_over_days_log
from eap_control.eap_tool import get_now
from tools.send_to_ui_tools import *
import settings

db = DbHandler()


class EapConfig:
    """
    Eap配置相关,比如id,ip和port,呼叫Eap间隔,机台连线模式Cim Mode, 机台操作模式等
    """
    __instance = None
    __initFlag = False
    __lock = threading.Lock()
    eapOnline = False

    def __new__(cls, *args, **kwargs):
        if cls.__instance is None:
            with cls.__lock:
                cls.__instance = super().__new__(cls)
        return cls.__instance

    def __init__(self):

        if not EapConfig.__initFlag:
            debug_eap("EapConfig.__init__() 进行初始化")
            EapConfig.__initFlag = True
            self.reaload_eap_config_params()
            self.userId = ""  # 默认是游客
            self.jobCount = 0  # 程序启动时候,这个值为1,就是设备中的板子的数量,来的时候+1,走的时候-1
            # 工位编号,默认主机台编号为01 Port代碼 01 = Port#01   02 = Port#02
            self.portNo = "01"
            # 制程分类 Default(预设) Inner(内层) Outer(外层) 这个值默认的不会改变
            self.productionMode = "Default"
            self.programVersion = "V2024.11.15.0"
            self.userName = ""
            self.nickName = ""
            self.deptId = "压合"
            # 各班的班别代码以及起讫时间,在机台上可以修改.
            # 班别代码 "1"  时间起 08:00  20:00  当日
            # 班别代码 "2" 时间起  20:00  08:00 前一日
            self.shiftId = "1"
            res, queueLotCount = db.get_lot_command_download_info()
            if res == "ok":
                queueCount = len(queueLotCount)
            else:
                queueCount = 0
            self.realStatusData = RealStatusData(self.cimMode, self.autoMode, self.userId,
                                                 self.idleTime, self.productionMode, self.programVersion)
            self.realStatusData.queueLotCount = queueCount
            # wip tracking report 相关信息
            self.prodHeight = 580
            self.prodWidth = 600
            self.prodCropThickness = 0.33
            self.prodCutSpeed = 1200
            self.prodCutDeep = 42
            self.startDt = get_now()
            # 当前上报的lotId
            self.lotId = "lot01"  # 上报的批次id
            self.outputQty = 0  # 本批次时机计算的数量
            self.lotQty = 0  # 基板数量(lot下发的数量)
            self.prodId = "001"  # 产品代码
            self.lotShortId = "lot01"  # 批号简写
            self.processCode = "default"  # 制程代码
            self.useInName = "压合"  # 产品用途
            self.layer = "0304"  # 层别
            self.stepSeq = "1"  # 步骤
            self.routeType = "1"  # 途程类型
            self.reworkRouteId = ""
            self.reworkStepSeq = ""  # 重工途程
            self.pnlSide = "C"  # 读码面次
            # UtilityReport 上报的相关内容,稼动率的计算,设备运行时间 / 总时间
            self.usePercent = 0.95
            self.totalRunTime = 0  # 设备运行的总时间
            self.prodEdge01 = 15
            self.prodEdge02 = 15
            self.prodEdge03 = 15
            self.prodEdge04 = 15

            self.planProdLotList = []

            self.camZmcIsRunning = False
            self.cbjZmcIsRunning = False
            self.bigCutterZmcIsRunning = False
            self.smallCutterZmcIsRunning = False

    def reaload_eap_config_params(self, sendToUi=False):
        """
        重新加载Eap的参数
        @return:
        """
        res, data = db.get_eap_config_params()
        if res != "ok":
            debug_eap(data)
        else:
            self.eqpId = data.get("eqp_id", "hd01")
            self.eqpIp = data.get("eqp_ip", "192.168.1.10")
            self.eqpPort = int(data.get("eqp_port", "8028"))
            self.eapIp = data.get("eap_ip", "192.168.1.20")
            self.eapPort = int(data.get("eap_port", "8026"))
            self.askDuration = int(data.get("ask_duration", "1800"))
            self.cimMode = data.get("cim_mode", "Local")
            self.autoMode = data.get("auto_mode", "自动模式")
            # 设备生产基板数量的历史记录(一直累加)
            self.historyJobCount = data.get("history_job_count", 0)
            self.idleTime = data.get("idle_delay_time", "60")
            self.prodMode = data.get("prod_mode", "")
            self.reqeustUrlFix = f"http://{self.eapIp}:{self.eapPort}/api/"
            # EquipmentCurrentLotReport 最近要生产的lot的列表,在接收到数据之后要放到这个列表中.
            self.eapLogDays = int(data.get("keep_log_days", 5))
            self.eapLogDir = data.get("eapLogDir", "")
            if self.eapLogDir == "":
                self.eapLogDir = settings.EAP_DEBUG_DIR
            self.RTMDuration = data.get("RTMDuration", 300)
            # 每次保存参数的时候去清理下日志,防止日志的天数被修改
            check_over_days_log()
            self.shiftId01 = data.get("shift_id_01", "1")
            self.shiftId02 = data.get("shift_id_02", "2")
            self.start01 = data.get("start_01", "08:00")
            self.end01 = data.get("end_01", "20:00")
            self.start02 = data.get("start_02", "20:00")
            self.end02 = data.get("end_02", "08:00")
            # 长度应该大于等于5才行.这里每次保存的时候需要注意.
            # 新增的一些配置,比如班别配置时间,还有生产的前5个lot数据.
            debug_eap(f"Eap参数加载成功:\n{data}")
            if sendToUi:
                # 这里表示保存了参数,保存了参数之后,要更新下status里面的数据
                self.realStatusData.cimMode = self.cimMode
                self.realStatusData.autoMode = self.autoMode
                self.realStatusData.idleDelay = self.idleTime
                self.realStatusData.prodMode = self.prodMode
                update_eap_config_to_ui([data])

    def send_init_data_to_ui(self):
        """
        更新后台的初始化参数到UI
        @return:
        """
        # 1. 更新eap_config_params表内容
        res, data = db.get_eap_config_params()
        newVal = []
        if res != "ok":
            debug_eap(data)
        else:
            newVal = [data]
        update_eap_config_to_ui(newVal)

        # 2. 更新Eap是否在线
        update_eap_status_to_ui(EapConfig.eapOnline)

        # 3. 更新当前登录的用户Id
        update_current_user_id(self.userId)

        # 5. lotCommandDownloadTable 表内容发送到前端
        update_lot_command_download_to_ui()

        # 6.  productionInfoDownLoad 表内容发送到前端
        update_prodinfo_download_to_ui()

    def reload_eap_user_login_info(self):
        """
        更新用户的id
        @return:
        """
        res, data = db.get_eap_user_info()
        if res != "ok":
            debug_eap(data)
        else:
            self.userId = data.get("user_id")
            self.realStatusData.userId = self.userId  # 更新userId的值
            self.userName = data.get("user_name")
            self.deptId = data.get("dept_id")
            self.shiftId = data.get("shift_id")
            self.nickName = data.get("nick_name")

    def get_rtm_infos(self):
        """
        :return:
        """
        data = db.get_working_info()[1]
        orderUsedKey = data.get("orderUsedKey", 0)
        knife_used = str(data.get("knifeUsed", 0))
        table_used_days = str(data.get("tableUsedDays", 1))
        orderUsed = db.get_order_by_key(orderUsedKey)
        jointNumber = orderUsed.get("jointNumber", "4")
        orderId = orderUsed.get("prod_id", "001")
        topEdge = orderUsed.get("topEdge", 15)
        leftEdge = orderUsed.get("leftEdge", 15)
        bottomEdge = orderUsed.get("bottomEdge", 15)
        rightEdge = orderUsed.get("rightEdge", 15)
        finished = orderUsed.get("finished", 0)
        data = db.get_cbj_zmc_params(db.cbjZmcParamsTable)[1]
        drag_speed = str(data.get("drag_speed", 500))
        rtm_list = []
        rtm_list.append({"item_id": "RTM01", "item_value": int(self.camZmcIsRunning)})
        rtm_list.append({"item_id": "RTM02", "item_value": int(self.cbjZmcIsRunning)})
        rtm_list.append({"item_id": "RTM03", "item_value": int(self.bigCutterZmcIsRunning)})
        rtm_list.append({"item_id": "RTM04", "item_value": int(self.smallCutterZmcIsRunning)})
        rtm_list.append({"item_id": "RTM05", "item_value": self.prodCutSpeed})
        rtm_list.append({"item_id": "RTM06", "item_value": drag_speed})
        rtm_list.append({"item_id": "RTM07", "item_value": topEdge})
        rtm_list.append({"item_id": "RTM08", "item_value": leftEdge})
        rtm_list.append({"item_id": "RTM09", "item_value": bottomEdge})
        rtm_list.append({"item_id": "RTM10", "item_value": rightEdge})
        rtm_list.append({"item_id": "RTM11", "item_value": self.prodCutDeep})
        rtm_list.append({"item_id": "RTM12", "item_value": jointNumber})
        rtm_list.append({"item_id": "RTM13", "item_value": orderId})
        rtm_list.append({"item_id": "RTM14", "item_value": knife_used})
        rtm_list.append({"item_id": "RTM15", "item_value": table_used_days})
        rtm_list.append({"item_id": "RTM16", "item_value": finished})
        rtm_infos = {
            "rtm": rtm_list
        }
        return rtm_infos

    def get_edc_infos(self):
        """
        获取edc_infos,就是 WIPTrackingReport 这个消息要上报的内容,格式类似这种
        "edc":
                [{
                    "item_id": ,
                    "item_value":
                 },
                 {
                    "item_id": ,
                    "item_value":
                 }],
        @return:
        """
        data = db.get_working_info()[1]
        knife_used = str(data.get("knifeUsed", 0))
        table_used_days = str(data.get("tableUsedDays", 1))
        data = db.get_cbj_zmc_params(db.cbjZmcParamsTable)[1]
        drag_speed = str(data.get("drag_speed", 500))
        work_speed = str(data.get("fx_work_speed", 1200))
        # 1. 内板长边尺寸
        # 2. 内板短边尺寸
        # 3. 铜箔厚度
        # 4. 圆刀使用寿命
        # 5. 台布使用寿命
        # 6. 切割速度
        # 7. 裁切机拖拽速度
        # 8. 裁切机工作速度
        # 9. 下刀深度
        edc_list = [{"item_id": "T001", "item_value": self.prodHeight},
                    {"item_id": "T002", "item_value": self.prodWidth},
                    {"item_id": "T003", "item_value": self.prodCropThickness},
                    {"item_id": "T004", "item_value": knife_used},
                    {"item_id": "T005", "item_value": table_used_days},
                    {"item_id": "T006", "item_value": self.prodCutSpeed},
                    {"item_id": "T007", "item_value": drag_speed},
                    {"item_id": "T008", "item_value": work_speed},
                    {"item_id": "T009", "item_value": self.prodCutDeep}]
        edc_infos = {
            "edc": edc_list
        }
        return edc_infos

    def get_utl__infos(self):
        """
        获取设备utl_infos ,类似下面这种,参考profile
        "utl_infos":
            {
                "utl": [{
                    "item_id": ,
                    "item_value":
                 },
                 {
                    "item_id": ,
                    "item_value":
                 }],
             }
        @return:
        """
        data = db.get_cbj_zmc_params(db.cbjZmcParamsTable)[1]
        drag_speed = str(data.get("drag_speed", 500))
        work_speed = str(data.get("fx_work_speed", 1200))
        utl_list = []
        # 1. 稼动率
        utl_list.append({"item_id": "U001", "item_value": self.usePercent}) #  float
        # 2. 设备总累积运行时间
        utl_list.append({"item_id": "U002", "item_value": self.totalRunTime}) # 使用小时 float
        # 3. 第一刀留边宽度
        utl_list.append({"item_id": "U003", "item_value": str(self.prodEdge01)})
        # 4. 第二刀留边宽度
        utl_list.append({"item_id": "U004", "item_value": str(self.prodEdge02)})
        # 5. 第三刀留边宽度

        utl_list.append({"item_id": "U005", "item_value": str(self.prodEdge03)})
        # 6. 第四刀留边宽度
        utl_list.append({"item_id": "U006", "item_value": str(self.prodEdge04)})
        # 7. 切割速度
        utl_list.append({"item_id": "U007", "item_value": str(self.prodCutSpeed)})
        # 8. 拖拽速度
        utl_list.append({"item_id": "U008", "item_value": str(work_speed)})
        # 9. 上料速度
        utl_list.append({"item_id": "U009", "item_value": str(drag_speed)})
        # 10. 下料速度
        utl_list.append({"item_id": "U010", "item_value": str(drag_speed)})
        # 11. 下刀深度
        utl_list.append({"item_id": "U011", "item_value": str(self.prodCutDeep)})
        utl_infos = {
            "utl": utl_list
        }
        return utl_infos

    #

    def reload_prod_lot_list(self):
        from eap_control.eap_request import request_eqp_current_lot_report
        res, data = db.get_lot_command_download_info()  # key越小越在前面
        if res == "ok":
            # 当planProdLotList的list小于5的时候,更新当前的作业任务
            if len(data) <= 5:
                self.planProdLotList = data[:5]
                # EquipmentCurrentLotReport  上报当前准备生产的批号ID
                request_eqp_current_lot_report()

